////////////////////////////////////////////////////////
// CodePlex - metacpp
//--------------------
// This file is part of "metacpp" project on CodePlex. The
// goal if the project is to demonstrate basic techniques
// used in C++ metaprogrammins.
// For more info and comments please visit:
// http://www.codeplex.com/metacpp/
////////////////////////////////////////////////////////

#include <iostream>

//////////////////////////////////////
// TEMPATE SPECIALIZATION

template<typename T>
void print(void) {
	std::cout << "Generic print" << std::endl;
}

template<>
void print<int>(void) {
	std::cout << "Int print" << std::endl;
}

void show_full_function_specialization(void) {
	std::cout << "FULL FUNCTION SPECIALIZATION:" << std::endl;
	print<char>();
	print<std::string>();
	print<int>();
}


//////////////////////////////////////
// VARIATIONS

template<typename T, typename U>
void show_specialization(T t, U u) {
	std::cout << "Generic version" << std::endl;
}

template<typename T>
void show_specialization(T t1, T t2) {
	std::cout << "Same type for both parameters" << std::endl;
}

template<typename NICK, typename PU>
void show_specialization(NICK *pt, PU *pu) {
	std::cout << "Pointer types used" << std::endl;
}


void show_full_function_specialization_variations(void) {
	std::cout << "FULL FUNCTION SPECIALIZATION VARIATIONS:" << std::endl;
	show_specialization(10, "str");
	
	int i1 = 1;
	int i2 = 2;
	char ch = 'c';
	int *pi = &i1;
	char *pch = &ch;
	show_specialization(i1, ch);
	show_specialization(i1, i2);
	show_specialization(pi, pch);
	show_specialization(pi, i1);
}